package com.pub.tools;

/**
 * <p>Title: </p>
 * <p>Description: </p>
 * <p>Copyright: Copyright (c) 2003</p>
 * <p>Company: </p>
 * @author not attributable
 * @version 1.0
 * @history
 * -----------------------------------------------------------
 * Tan Chen            08/20/2003          Modify.
 */

import java.util.*;
import java.io.*;
import org.apache.commons.io.FilenameUtils;
import com.pub.database.QueryBean;
import javax.servlet.http.HttpServletResponse;

/**
 * An Attach Bean to add, delete, get, ... an Attach file.
 * AttachBean allow multi attach files.
 */

public class AttachBean {

    //following are add for attach file
    private Hashtable<String,Integer> athHsh = null;
    //為了增加多個檔案,最多30個,將attachitem取消,所以這邊用陣列去接
    private String[] athID = new String[30]; //Attach File ID ( File Name)
    private String[] athExt = new String[30]; //Attach File Extend Express(.txt)
    private String[] athMimeType = new String[30]; //Attach File Mime Type
    private byte[][] athBinaryData = new byte[30][]; //Attach File Data (Binary)
    private int elmKey = 1; //陣列元素的key值

    //private ParsePosition pp = new ParsePosition(0); //字串格式->日期格式
    //private FieldPosition fp = new FieldPosition(0); //日期格式->字串格式
    //private SimpleDateFormat sdf = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss"); //設定格式化物件

    //private PropertyBean  rb = new PropertyBean("TS");
    //private String jspBase = rb.getString("dirJSP");
    //private String svlBase = rb.getString("dirSvl");

    //private int HashNo = 0;

    public AttachBean() {}
/*
    private String big5(String str) {
        if (str == null) {
            return null;
        }
        String big5Str = str;
        try {
            big5Str = new String(str.getBytes("8859_1"), "Big5");
        } catch (java.io.UnsupportedEncodingException ue) {
            System.out.println("System Not Support Big5 Character Set:" +
                               ue.toString());
        }
        return big5Str;
    }*/

    /*********** Following are add for attach File *****************/
    /**
     * Get FileName List of Attached Files
     * @return String. The FileName List of Attached Files.
     */
    public String getathselectForm() {
        //HashNo = 0;
        if (athHsh == null) {
            return "";
        } else {
            Vector<String> athVec = new Vector<String>(athHsh.keySet());
            if (athVec != null) {
                String retStr = "";
                for (int i = 0; i < athVec.size(); i++) {
                    retStr = retStr + "<OPTION>" + (String) athVec.elementAt(i) +
                             "</OPTION>";
                }
                return retStr;
            } else {
                return "";
            }
        }
    }

    /**
     * Get FileName List of Attached Files
     * @param showtype. The Show Type.
     * @param func. The Function Name.
     * @return String. The FileName List of Attached Files.
     */
    public String getathlist(String showtype, String func) {
        if (athHsh == null) {
            return "";
        } else {
            Vector<String> athVec = new Vector<String>(athHsh.keySet());
            if (athVec != null) {
                String retStr = "";
                for (int i = 0; i < athVec.size(); i++) {
                    if (retStr.length() == 0) {
                        retStr = (String) athVec.elementAt(i);
                    } else {
                        retStr = retStr + "," + (String) athVec.elementAt(i);
                    }
                }
                return retStr;
            } else {
                return "";
            }
        }
    }

    /**
     * Add Attached File to Attach Hash
     * @param fName. The File Name.
     * @param fExt. The Extend Express of Attach File.
     * @param fMimeType. The Mime Type of Attach File.
     * @param fData. The File Data of Attach File.
     */
    public void addAttach(String fName, String fExt, String fMimeType,
                          byte[] fData) {
        if (fName == null || fData == null) {
            return;
        }
        String lathID = fName.toUpperCase();
        if (athHsh == null) {
            athHsh = new Hashtable<String,Integer>();
        }
        if (athHsh.containsKey(lathID)) {
            athHsh.remove(lathID);
        }
        //athHsh.put(athID, new AttachItem(athID,fExt,fMimeType,fData) );
        athID[elmKey] = lathID;
        athExt[elmKey] = fExt;
        athMimeType[elmKey] = fMimeType;
        athBinaryData[elmKey] = fData;
        athHsh.put(lathID, new Integer(elmKey++));
    }

    /**
     * Get File Data of Attached File
     * @param  fName. The File Name.
     * @return byte[]. The File Data of Attached File.
     */
    public byte[] getAttach(String fName) {
        Integer keynumber;
        byte[] ret = null;
        if (fName == null) {
            return ret;
        }
        String athID = fName.toUpperCase();
        if (athHsh.containsKey(athID)) {
            //AttachItem ai = (AttachItem)athHsh.get(athID);
            //ret = ai.getathBinaryData();
            keynumber = (Integer) athHsh.get(athID);
            ret = athBinaryData[keynumber.intValue()];
        }
        return ret;
    }

    /**
     * Get Content Type of Attached File
     * @param  fName. The File Name.
     * @return String. The Content Type of Attached File.
     */
    public String getContentType(String fName) {
        String ret = null;
        Integer keynumber;
        if (fName == null) {
            return ret;
        }
        String athID = fName.toUpperCase();
        if (athHsh.containsKey(athID)) {
            //AttachItem ai = (AttachItem)athHsh.get(athID);
            //ret = ai.getathMimeType();
            keynumber = (Integer) athHsh.get(athID);
            ret = athMimeType[keynumber.intValue()];
        }
        return ret;
    }

    /**
     * Delete Attached File
     * @param  fName. The File Name.
     * @return boolean. True,if the file removed success.
     */
    public boolean delAttach(String fName) {
        if (fName == null || fName.equals("")) {
            return false;
        }
        String athID = fName.toUpperCase();
        if (athHsh.containsKey(athID)) {
            athHsh.remove(athID);
            return true;
        }
        return false;
    }

    public static String getFilename(String fullname) {
        String filename = null;
        fullname = fullname.replace('\\', '/');
        StringTokenizer token = new StringTokenizer(fullname, "/");
        while (token.hasMoreTokens()) {
            filename = token.nextToken();
        }
        return filename;
    }

    public static String getExtension(String pstrFileName){
        return FilenameUtils.getExtension(pstrFileName);
    }

    public String downloadAttach(HttpServletResponse response,QueryBean pqbnDAO,String pstrTableName,String pstrFlowCode,String pstrFileID)throws Exception{
        String lstrFileExtName=null;
        Hashtable<String,Object> lhtFileInfo=null;
        String lstrFileName=null;
        byte[] bteData=null;
        FileInputStream finFile = null;

        try{
            lhtFileInfo=pqbnDAO.readSingleRowData("select file_name,mime_type,file_storage,file_path from " + pstrTableName + " where flow_code='" + pstrFlowCode + "' and file_id='" + pstrFileID + "'");

            lstrFileName=lhtFileInfo.get("FILE_NAME").toString();

            lstrFileExtName=AttachBean.getExtension(lhtFileInfo.get("FILE_NAME").toString());

            //file實體存在table中
            if(lhtFileInfo.get("FILE_STORAGE").toString().equals("DB")){
                bteData=(byte[])pqbnDAO.readSingleRowData("select file_data from " + pstrTableName + " where flow_code='" + pstrFlowCode + "' and file_id='" + pstrFileID + "'").get("FILE_DATA");
            }
            else{//file 存於 file server中
                finFile=new FileInputStream(lhtFileInfo.get("FILE_PATH").toString() + "/" + pstrFlowCode + pstrFileID + "." + lstrFileExtName);
                bteData=new byte[finFile.available()];
                finFile.read(bteData);
            }

            response.setContentType(lhtFileInfo.get("MIME_TYPE").toString());

            //設定另存新檔的檔名，(可以存中文，國際化時要拿掉 String(lhtFileInfo.get("FILE_NAME").toString().getBytes("Big5"), "ISO8859_1") )
            response.addHeader("Content-Disposition",
                   "inline;filename=" +
                   new
                   String(lhtFileInfo.get("FILE_NAME").toString().getBytes("Big5"), "ISO8859_1") +
                   (lstrFileExtName.equals("JPG") || lstrFileExtName.equals("GIF") || lstrFileExtName.equals("BMP") ? "" : ";attachment"));

            OutputStream ou = response.getOutputStream();
            ou.write(bteData);
            ou.close(); //這行是衛聖在QueryBean加上去的，也是唯一與PMD解附檔有差異的地方，Office文件無法開啟，不知是否為此差異??



            //要記得加上以下這二行指令 (避免主機出現 Connection rest by peer的錯誤訊息)
            response.setStatus(HttpServletResponse.SC_OK);
            response.flushBuffer();

            return lstrFileName;
        }
        catch(Exception e){
            System.out.println("can't open attachment for DB!!");
            System.out.println("table name==>" + pstrTableName);
            System.out.println("flow code==>" + pstrFlowCode);
            System.out.println("file id==>" + pstrFileID);
            throw new Exception(e);
        }
        finally{
            if(lhtFileInfo!=null){
                lhtFileInfo.clear();
                lhtFileInfo=null;
            }
        }
    }
}
